package com.traffic.between.service;

import java.net.URI;
import java.nio.charset.Charset;
import java.security.MessageDigest;

import org.apache.http.HttpEntity;
import org.apache.http.HttpResponse;
import org.apache.http.HttpStatus;
import org.apache.http.client.HttpClient;
import org.apache.http.client.methods.HttpGet;
import org.apache.http.impl.client.DefaultHttpClient;
import org.apache.http.params.CoreConnectionPNames;
import org.apache.http.util.EntityUtils;
import org.apache.log4j.Logger;

import com.traffic.between.config.BetweenProperties;
import com.traffic.between.util.Xml2JsonUtil;

import net.sf.json.JSONObject;

@SuppressWarnings("deprecation")
public class YunShangServiceImpl {
	private static Logger logger = Logger.getLogger(YunShangServiceImpl.class);
	public static YunShangServiceImpl service = new YunShangServiceImpl();

	private static String HOST_ORDER_PATH = BetweenProperties.YSLL_ORDER_URL;
	private static String HOST_ORDERSTATUS_PATH = BetweenProperties.YSLL_ORDERSTATUS_URL;
	private static String YSLL_APPKEY = BetweenProperties.YSLL_APPKEY;
	private static String YSLL_SECURITYKEY = BetweenProperties.YSLL_SECURITYKEY;

	@SuppressWarnings({ "resource" })
	public String order(String productId, String phoneNo, String cstmOrderNo) {
	
		String result = "";
		// 订单状态回调通知地址,暂不适用
		String notifyUrl = "";

		/**
		 * 排序后的待加密的签名
		 * 
		 * tbOrderNo 订单号，唯一 spuId 产品编号，由云上分配 supplierId 渠道商编号 accountVal 手机号
		 */
		String signstr = "accountVal" + phoneNo + "spuId" + productId + "supplierId" + YSLL_APPKEY + "tbOrderNo"
				+ cstmOrderNo;
		signstr = signstr + YSLL_SECURITYKEY;

		// md5加密后sign
		String sign = getMD5(signstr);

		String param = "tbOrderNo=" + cstmOrderNo + "&spuId=" + productId + "&accountVal=" + phoneNo + "&supplierId="
				+ YSLL_APPKEY + "&notifyUrl=" + notifyUrl + "&sign=" + sign;
		logger.info("between- 云上流量订购请求参数 params<>"+param);
		HttpClient httpClient = new DefaultHttpClient();
		// 连接时间，指的是连接一个url的连接等待时间。 超时报异常
		httpClient.getParams().setParameter(CoreConnectionPNames.CONNECTION_TIMEOUT, 30000);
		// 数据传输时间，指的是连接上一个url，获取response的返回等待时间
		httpClient.getParams().setParameter(CoreConnectionPNames.SO_TIMEOUT, 40000);
		// Get请求
		HttpGet httpget = new HttpGet(HOST_ORDER_PATH);
		try {
			httpget.setURI(new URI(httpget.getURI().toString() + "?" + param));

			// 发送请求
			HttpResponse httpResponse = httpClient.execute(httpget);
			int statusCode = httpResponse.getStatusLine().getStatusCode();

			if (statusCode != HttpStatus.SC_OK) {
				logger.error("Method failed:" + httpResponse.getStatusLine());
				return "{\"resultCode\": \"01\",\"resultMsg\":\"订单异常\"}";
			}

			// 获取返回数据
			HttpEntity entity = httpResponse.getEntity();
			String body = EntityUtils.toString(entity, Charset.forName("UTF-8"));
			logger.info("between- 云上流量订购请求响应body :" + body);
			// 将xml格式转为json
			String bodyJson = Xml2JsonUtil.xml2JSON(body);

			JSONObject resultJson = JSONObject.fromObject(bodyJson);

			// {"response":{"errorDesc":"xxx","errorCode":"xxx","coopOrderStatus":"xxx","coopOrderNo":"xxx"}}
			JSONObject json = (JSONObject) resultJson.get("response");
			logger.info("between- 云上流量订购请求响应xml2Json  json:" + json);
			// 订单状态，可选值如下：SUCCESS 订单充值成功FAILED 订单充值失败 UNDERWAY 订单充值中
			// ORDER_NOT_EXIST 订单不存在
			String coopOrderStatus = (String) json.get("coopOrderStatus");
			if ("SUCCESS".equals(coopOrderStatus)) {
				result = "{\"resultCode\": \"00\",\"resultMsg\":\"订单充值成功\"}";
			} else if ("FAILED".equals(coopOrderStatus)) {
				result = "{\"resultCode\": \"01\",\"resultMsg\":\"订单充值失败\"}";
			} else if ("UNDERWAY".equals(coopOrderStatus)) {
				result = "{\"resultCode\": \"02\",\"resultMsg\":\"订单充值中\"}";
			} else {
				result = "{\"resultCode\": \"03\",\"resultMsg\":\"订单不存在\"}";
			}
			if (entity != null) {
				EntityUtils.consume(entity);
			}

		} catch (Exception e) {
			e.printStackTrace();
		} finally {
			httpget.releaseConnection();
			httpClient.getConnectionManager().shutdown();
		}
		return result;
	}

	@SuppressWarnings({ "resource" })
	public String orderStatus(String cstmOrderNo) {

		logger.info("between- 云上流量订购状态请求参数: params cstmOrderNo = " + cstmOrderNo);

		String result = "";

		/**
		 * 排序后的待加密的签名
		 * 
		 * tbOrderNo 订单号，唯一
		 */
		String signstr = "supplierId" + YSLL_APPKEY + "tbOrderNo" + cstmOrderNo + YSLL_SECURITYKEY;

		// md5加密后sign
		String sign = getMD5(signstr);

		String param = "tbOrderNo=" + cstmOrderNo + "&supplierId=" + YSLL_APPKEY + "&sign=" + sign;

		HttpClient httpClient = new DefaultHttpClient();
		// 连接时间，指的是连接一个url的连接等待时间。 超时报异常
		httpClient.getParams().setParameter(CoreConnectionPNames.CONNECTION_TIMEOUT, 20000);
		// 数据传输时间，指的是连接上一个url，获取response的返回等待时间
		httpClient.getParams().setParameter(CoreConnectionPNames.SO_TIMEOUT, 10000);
		// Get请求
		HttpGet httpget = new HttpGet(HOST_ORDERSTATUS_PATH);
		try {
			httpget.setURI(new URI(httpget.getURI().toString() + "?" + param));

			// 发送请求
			HttpResponse httpResponse = httpClient.execute(httpget);
			int statusCode = httpResponse.getStatusLine().getStatusCode();

			if (statusCode != HttpStatus.SC_OK) {
				logger.error("Method failed:" + httpResponse.getStatusLine());
				return "{\"resultCode\": \"01\",\"resultMsg\":\"订单异常\"}";
			}

			// 获取返回数据
			HttpEntity entity = httpResponse.getEntity();
			String body = EntityUtils.toString(entity, Charset.forName("UTF-8"));
			logger.info("between- 云上流量订购请求状态响应body :" + body);
			// 将xml格式转为json
			String bodyJson = Xml2JsonUtil.xml2JSON(body);

			JSONObject resultJson = JSONObject.fromObject(bodyJson);

			// {"response":{"errorDesc":"xxx","errorCode":"xxx","coopOrderStatus":"xxx","coopOrderNo":"xxx"}}
			JSONObject json = (JSONObject) resultJson.get("response");
			logger.info("between- 云上流量订购请求状态响应xml2Json  json:" + json);
			// 订单状态，可选值如下：SUCCESS 订单充值成功FAILED 订单充值失败 UNDERWAY 订单充值中
			// ORDER_NOT_EXIST 订单不存在
			String coopOrderStatus = (String) json.get("coopOrderStatus");
			if ("SUCCESS".equals(coopOrderStatus)) {
				result = "{\"resultCode\": \"00\",\"resultMsg\":\"订单充值成功\"}";
			} else if ("FAILED".equals(coopOrderStatus)) {
				result = "{\"resultCode\": \"01\",\"resultMsg\":\"订单充值失败\"}";
			} else if ("UNDERWAY".equals(coopOrderStatus)) {
				result = "{\"resultCode\": \"02\",\"resultMsg\":\"订单充值中\"}";
			} else if ("ORDER_NOT_EXIST".equals(coopOrderStatus)) {
				result = "{\"resultCode\": \"03\",\"resultMsg\":\"订单不存在\"}";
			}else {
				result = "{\"resultCode\": \"02\",\"resultMsg\":\"订单充值中\"}";
			}
			if (entity != null) {
				EntityUtils.consume(entity);
			}

		} catch (Exception e) {
			e.printStackTrace();
			logger.error("between- 云上流量订购请求上游异常:" + e);
		} finally {
			httpget.releaseConnection();
			httpClient.getConnectionManager().shutdown();
		}
		return result;
	}

	/**
	 * md5加密 ，用于生成sign
	 * 
	 * @param message
	 * @return
	 */
	public static String getMD5(String message) {
		MessageDigest messageDigest = null;
		StringBuffer md5StrBuff = new StringBuffer();
		try {
			messageDigest = MessageDigest.getInstance("MD5");
			messageDigest.reset();
			messageDigest.update(message.getBytes("UTF-8"));

			byte[] byteArray = messageDigest.digest();
			for (int i = 0; i < byteArray.length; i++) {
				if (Integer.toHexString(0xFF & byteArray[i]).length() == 1)
					md5StrBuff.append("0").append(Integer.toHexString(0xFF & byteArray[i]));
				else
					md5StrBuff.append(Integer.toHexString(0xFF & byteArray[i]));
			}
		} catch (Exception e) {
			throw new RuntimeException();
		}
		return md5StrBuff.toString().toLowerCase();// 字母小写
	}
}
